// AllTabs.cpp : implementation file
//

#include "stdafx.h"
#include "moretunes.h"
#include "AllTabs.h"
#include ".\alltabs.h"
#include "misc.h"
#include "shareware.h"
#include "KickStart.h"

// CAllTabs

IMPLEMENT_DYNAMIC(CAllTabs, CResizableSheet)
CAllTabs::CAllTabs(UINT nIDCaption, CPrefTab *prefs, CWnd* pParentWnd, UINT iSelectPage)
	:CResizableSheet(nIDCaption, pParentWnd, iSelectPage)
	, _xmlExtractor()
	, _progress(0)
	, _similar(FALSE)
	, _pages(0)
	, _grabXmlList(this, 0, prefs)
	, _grabPicList(this, 1, prefs)
	, _miscGrabber(this, 3, prefs)
	, _prefs(prefs)
	, _trayNot(0)
	, _bigPicture(0)
	, _artistName(_T(""))
{
}

CAllTabs::CAllTabs(LPCTSTR pszCaption, CPrefTab *prefs, CWnd* pParentWnd, UINT iSelectPage)
	:CResizableSheet(pszCaption, pParentWnd, iSelectPage)
	, _xmlExtractor()
	, _progress(0)
	, _similar(FALSE)
	, _pages(0)
	, _grabXmlList(this, 0, prefs)
	, _grabPicList(this, 1, prefs)
	, _miscGrabber(this, 3, prefs)
	, _prefs(prefs)
	, _trayNot(0)
{
}

CAllTabs::~CAllTabs()
{
}

#define WM_ICON_NOTIFY  WM_APP+10
//CSystemTray m_TrayIcon;

BEGIN_MESSAGE_MAP(CAllTabs, CResizableSheet)
//ON_WM_PAINT()
ON_MESSAGE(WM_ICON_NOTIFY, OnTrayNotification)
ON_WM_DESTROY()
ON_WM_SYSCOMMAND()
ON_COMMAND(ID_RESTORE, OnRestore)
ON_COMMAND(ID_SHOWMAINWINDOW, OnShowMainWindow)
ON_COMMAND(ID_SHOWMINI, OnShowMini)
ON_WM_HELPINFO()
ON_WM_WINDOWPOSCHANGED()
END_MESSAGE_MAP()

#define PROGRESS_STEP 6
#define PROGRESS_STEP_PIC 1

BOOL CAllTabs::checkDownload(void) {
	if (downloadXml() && downloadPic()) {
		if (_bigPicture == FALSE)
			finalizeLoading();
		else {
			_albumsTab->_coverTab->setResult(_albumsTab->_currentAlbum);// dirty but works well
			return TRUE;
		}

		return TRUE;
	}
	return FALSE;
}

#define MAX_PAGES 9

BOOL CAllTabs::downloadXml(void)
{
	if (_grabXmlList.isEmpty())
		return TRUE;

	// Read the file
	CString str = _grabXmlList.getFileName();
	_grabXmlList.cutHead();
	if (_grabXmlList._stop == FALSE)
		_xmlExtractor.loadFile(str);

	// Download the other pages, do this only the first time
	if (_pages == 0 && !_similar) {
		if (((_pages = _xmlExtractor.getPages()) == -1))
			return TRUE;
		if (_pages == -2) {
//			if (!_grabXmlList.downloadFile(computeURL(_xmlExtractor.getId(), 1), computeFilename(_xmlExtractor.getId(), 1)))
			if (!_grabXmlList.downloadFile(computeURL(_artistName, 1), computeFilename(_artistName, 1)))
				return TRUE;
		}
		else {
			if (_pages > MAX_PAGES)
				_pages = MAX_PAGES;
			for (int page = 2; page <= _pages; page++)
//				_grabXmlList.downloadFile(computeURL(_xmlExtractor.getId(), page), computeFilename(_xmlExtractor.getId(), page));
				_grabXmlList.downloadFile(computeURL(_artistName, page), computeFilename(_artistName, page));
		}
	}

	// Broadcast the new stuffs
	_albumsTab->setResult(_xmlExtractor.getAlbums());
	updateProgession(PROGRESS_STEP);

	// The xml is downloaded. Download the pictures
	if (_grabXmlList.isEmpty()) {
		CList<Album*, Album*>	*albums = _xmlExtractor.getAlbums();
		Album* album;
		if (!albums || albums->GetCount() == 0 || _prefs->_coverArtData == FALSE)
			return TRUE;
		POSITION pos = albums->GetHeadPosition();
		for (int i = 0; i < albums->GetCount(); i++)
		{
			album = albums->GetNext(pos);
			if (!album->getImageUrl().IsEmpty()) {
				_grabPicList.downloadFile(album->getImageUrl(), album->getImageFile());
			}
		}
		_grabPicList.Download();
	}
	return FALSE;
}

BOOL CAllTabs::downloadPic(void)
{
	// if it's empty
	if (_grabPicList.isEmpty())
		return TRUE;

	// Remove the downloaded one so the next can start
	CString str = _grabPicList.getFileName();
	_grabPicList.cutHead();

	// If the file is too small, it's rotten. We can delete it
	CFile fp;
	if (fp.Open(str, CFile::modeRead)) {
		if (fp.GetLength() < BAD_PIC_SIZE) {
			fp.Close();
			if (str.Find("_B") == -1) // don't delete big pics it sucks!
				DeleteFile(str);
		}
	}

	// Broadcast the new stuffs
	updateProgession(PROGRESS_STEP_PIC);
	if (_grabPicList.isEmpty()) {
		SetTitle(TITLE_MORETUNES);
		return TRUE;
	}
	return FALSE;
}

BOOL CAllTabs::downloadAlbums(CString name, BOOL reload, BOOL connect)
{
	// Init some stuffs
	_xmlExtractor.initExtractor(purifyName(name));
	_albumsTab->setResult(NULL);
	_grabPicList._stop = FALSE;
	_grabXmlList._stop = FALSE;
	_bigPicture = FALSE;
	_artistName = name;

	// If it's already in cache
	CFileFind file;
	if (reload == FALSE && file.FindFile(computeFilename(name, 1))) {
		file.Close();
		return loadCache(name);
	}
	if (connect == FALSE) {
		if (file.FindFile(computeFilename(name, 1))) {
			file.Close();
			return loadCache(name);
		}
		return FALSE;
	}

	// Start the first download
	if (!_grabXmlList.isEmpty())
		return finalizeLoading();
	if (!_grabXmlList.downloadFile(computeURL(name, 1), computeFilename(name, 1)))
		return finalizeLoading();
	_grabXmlList.Download();
	updateProgession(NULL);
	return TRUE;
}

int CAllTabs::downloadBigPic(void) {
	Album *album = _albumsTab->_currentAlbum;

	if (album == NULL || _albumsTab->_searching)
		return 0;

	// Test if the image exists
	CFileFind file;
	if (file.FindFile(album->getImageLargeFile()) || !file.FindFile(album->getImageFile())) {
		file.Close();
		return 0;
	}

	// if not download it
	_bigPicture = TRUE;
	if (album->getImageLargeUrl().IsEmpty())
		return 0;
	if (!_grabPicList.downloadFile(album->getImageLargeUrl(), album->getImageLargeFile()))
		return 0;
	_grabPicList.Download();
	updateProgession(NULL);
	return 1;
}

BOOL CAllTabs::downloadSimilar(Album *album) {
	if (!album)
		return FALSE;
	_similar = TRUE;
	return downloadAlbums(album->getAsin(), FALSE, TRUE);
}

BOOL CAllTabs::loadCache(CString name)
{
	_xmlExtractor.loadFile(computeFilename(name, 1));
	if (((_pages = _xmlExtractor.getPages()) > 1))
		for (int page = 2; page <= _pages; page++)
			_xmlExtractor.loadFile(computeFilename(name, page));
	finalizeLoading();
	return TRUE;
}

BOOL CAllTabs::finalizeLoading(void)
{
	// A little cleaning
	_albumsTab->_currentAlbum = NULL;
	_albumsTab->setSearchReady(_xmlExtractor.getAlbums());
	SetTitle(TITLE_MORETUNES);
	_pages = 0;
	_similar = FALSE;
	return FALSE;
}


CString CAllTabs::computeURL(CString name, int page)
{
	CString			url;
	
	url = _prefs->getServer();
	if (_similar == TRUE) {
		url += "SimilaritySearch=";
		url += name;
	}
	else {
		url += "Artist=";
		url += purgeName(name);
	}
	url += "&ItemPage=";
	url.Format("%s%d", url, page);
	return url;
}

BOOL CAllTabs::initPages(CAlbumsTab *albumsTab)
{
	_albumsTab = albumsTab;
	return TRUE;
}

//void CAllTabs::OnPaint()
//{
//	CPaintDC dc(this); // device context for painting
//	_albumsTab->_refresh = FALSE;
//	_albumsTab->_coverTab->_refresh = FALSE;
//	_albumsTab->_reviewTab->_refresh = FALSE;
//}

BOOL CAllTabs::updateProgession(int step)
{
	if (step == NULL)
		_progress = NULL;
	else
		_progress += step;
	float f;
	f = (float)_progress/((float) _pages * 15) * 100;
	f = (f>100) ? (100): f;
	CString str;
	str.Format("%s %d %%", TITLE_DOWNLOADING, (int)f);
	SetTitle(str);
//	_albumsTab->_artist.SetWindowText(str);
	_albumsTab->_miniWnd._status.SetWindowText(str);
	return FALSE;
}

int CAllTabs::checkVersion(void)
{
	return 0;
}

BOOL CAllTabs::OnInitDialog()
{
	BOOL bResult = CResizableSheet::OnInitDialog();

	HICON icon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
	SetIcon(icon, TRUE);			// Set big icon

	// add the minimize button to the window
	::SetWindowLong( m_hWnd, GWL_STYLE, GetStyle() | WS_MINIMIZEBOX );

	// add the minimize command to the system menu
	GetSystemMenu( FALSE )->InsertMenu( -1, MF_BYPOSITION | MF_STRING,
		SC_ICON, "Minimize" );

	SetActivePage(TAB_ID3);
	SetActivePage(TAB_ALBUMS);

	HICON icon2 = AfxGetApp()->LoadIcon(IDI_MINIMIZE);
	_trayNot = new CTrayNot(this,WM_ICON_NOTIFY, NULL,&icon2);
	_trayNot->SetState(IDR_MAINFRAME);

	// Set the window size and pos
	CRect fullRect;
	GetWindowRect(fullRect); // absolute position
	int top = fullRect.top - _prefs->_heigthData / 2;
	if (top < 0)
		top = 0;
	if (_prefs->_windowLeft < 3000 && _prefs->_windowLeft > -3000 && _prefs->_windowTop >= 0)
		SetWindowPos(this, _prefs->_windowLeft, _prefs->_windowTop, 0
			, fullRect.bottom - fullRect.top + _prefs->_heigthData, 
			SWP_NOZORDER | SWP_SHOWWINDOW); // relative position
	else 
		SetWindowPos(this, fullRect.left, top, 0
			, fullRect.bottom - fullRect.top + _prefs->_heigthData, 
			SWP_NOZORDER | SWP_SHOWWINDOW); // relative position

	LoadAccelerators(AfxGetInstanceHandle (), MAKEINTRESOURCE (IDR_ACCELERATOR1));

	if (_prefs->_firstTime == TRUE) {
		CKickStart ks;
		ks.DoModal();
	}
	else if (_prefs->_registration != REGISTRATION_OK) {
		CShareware shareware;
		shareware.DoModal();
	}
	return bResult;
}

LRESULT CAllTabs::OnTrayNotification(WPARAM wParam, LPARAM lParam) {
	switch (lParam)
	{
	case WM_RBUTTONDOWN:
		{
			CMenu menu ;
			VERIFY(menu.LoadMenu(IDR_SYSTRAY));
			CMenu* pPopup = menu.GetSubMenu (0) ;
			ASSERT(pPopup != NULL);
			// Get the cursor position
			POINT pt ;
			GetCursorPos (&pt) ;
			// Fixes Microsofts' BUG!!!!
			SetForegroundWindow();
			pPopup->TrackPopupMenu(TPM_LEFTALIGN | TPM_RIGHTBUTTON,pt.x, pt.y, AfxGetMainWnd());
			break ;
		}
	case WM_LBUTTONUP:
	case WM_LBUTTONDBLCLK:
		ShowWindow(SW_RESTORE);
		SetForegroundWindow();
		break ;
	}
	return 0;
}

#define KEY_STATE_UP 257
BOOL CAllTabs::PreTranslateMessage(MSG* pMsg) {
	if(pMsg->wParam == VK_F5 && pMsg->message == KEY_STATE_UP) {
		_albumsTab->OnReload();
	}
	else if(pMsg->wParam == VK_F6 && pMsg->message == KEY_STATE_UP) {
		_albumsTab->OnLyrics();
	}
	else if(pMsg->wParam == VK_F2 && pMsg->message == KEY_STATE_UP) {
		OnShowMini();
	}
	//else if(pMsg->wParam == VK_F2 && pMsg->message == KEY_STATE_UP && _prefs->_systrayData == TRUE) {
	//	theApp.HideApplication();
	//}
	//if(pMsg->wParam == VK_ESCAPE && pMsg->message == KEY_STATE_UP) {
	//	if (_albumsTab->_searching == TRUE)
	//		_albumsTab->OnBnClickedFind();
	//}
	return CResizableSheet::PreTranslateMessage(pMsg);
}
void CAllTabs::OnDestroy()
{
	CResizableSheet::OnDestroy();
	if (_trayNot)
	{
		delete _trayNot;
		_trayNot = NULL ;
	}
}

void CAllTabs::OnSysCommand(UINT nID, LPARAM lParam) {
	if (_prefs->_systrayData == TRUE)
	if (nID == SC_CLOSE) {
		theApp.HideApplication();
		return;
	}
	CResizableSheet::OnSysCommand(nID, lParam);
}

void CAllTabs::OnRestore(void) {
	ShowWindow (SW_RESTORE);
}

BOOL CAllTabs::OnHelpInfo(HELPINFO* pHelpInfo) {
	HtmlHelp(NULL, NULL);
	return NULL;
}

void CAllTabs::OnWindowPosChanged(WINDOWPOS* lpwndpos) {
	CResizableSheet::OnWindowPosChanged(lpwndpos);
	// Because the function is called during init...
	if (_trayNot == NULL)
		return;
	_prefs->_windowTop = lpwndpos->y;
	_prefs->_windowLeft = lpwndpos->x;
	_prefs->saveData();
}

void CAllTabs::OnShowMainWindow(void) {
	_albumsTab->_miniWnd.ShowWindow(SW_HIDE);
	this->ShowWindow(SW_SHOW);
	_prefs->_mini = FALSE;
	_prefs->saveData();
	_albumsTab->_miniWnd.SetWindowPos(this, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE);
//	_albumsTab->_miniWnd.SetOwner(this);
}

void CAllTabs::OnShowMini(void) {
	_albumsTab->_miniWnd.ShowWindow(SW_SHOW);
	this->ShowWindow(SW_HIDE);
	_prefs->_mini = TRUE;
	_prefs->saveData();
	_albumsTab->_miniWnd.SetWindowPos(&this->wndTopMost, 0, 0, 0, 0, SWP_NOMOVE|SWP_NOSIZE);
//	_albumsTab->_miniWnd.SetOwner((CWnd *)&this->wndTopMost);
}
